package org.fhawk.tinyspring.mvc;


import org.apache.commons.lang.StringUtils;
import org.fhawk.tinyspring.core.ClassHelper;
import org.fhawk.tinyspring.ioc.BeanHelper;
import org.fhawk.tinyspring.mvc.annotation.Controller;
import org.fhawk.tinyspring.mvc.annotation.Requset;
import org.fhawk.tinyspring.mvc.bean.Handler;
import org.fhawk.tinyspring.mvc.bean.Requester;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.lang.reflect.Method;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.ConcurrentHashMap;

/**
 * Created by tuo on 9/5/2016.
 */
public class ActionHelper {
    private static final Map<Requester, Handler> actionMap = new ConcurrentHashMap<>();
    private static Logger logger = LoggerFactory.getLogger(ActionHelper.class);
    private static final String URL_SEPARATOR = "/";

    private ActionHelper() {
    }

    static {
        try {
            List<Class<?>> classes = ClassHelper.getBasePackageClassListByAnnotation(Controller.class);
            for (Class<?> clazz : classes) {
                Method[] methods = clazz.getDeclaredMethods();
                for (Method method : methods) {
                    if (method.isAnnotationPresent(Requset.class)) {
                        Requset requset = method.getAnnotation(Requset.class);
                        String path = StringUtils.isEmpty(requset.value()) ? method.getName() : requset.value();
                        //对于所有路径前面没有‘/’的路径全部加上'/'
                        path = path.startsWith("/") ? URL_SEPARATOR + path : path;
                        Requester requester = new Requester(requset.method().value(), path);
                        Method proxyMethod = BeanHelper.getBean(clazz).getClass().getMethod(method.getName(), method.getParameterTypes());
                        if (Objects.nonNull(proxyMethod)) {
                            method = proxyMethod;
                        }
                        Handler handler = new Handler(clazz, method);
                        logger.debug("{}", requester);
                        actionMap.put(requester, handler);
                    }
                }
            }
        } catch (NoSuchMethodException e) {
            logger.error("获取方法失败", e);
        }
    }

    public static Map<Requester, Handler> getActionMap() {
        return actionMap;
    }

    static Handler handler(Requester requester) {
        for (Map.Entry<Requester, Handler> entry : actionMap.entrySet()) {
            Requester mapRequester = entry.getKey();
            if (mapRequester.getMethod().equals(requester.getMethod()) && mapRequester.getPath().equals(requester.getPath())) {
                return entry.getValue();
            }
        }
        return null;
    }


}
